home *** CD-ROM | disk | FTP | other *** search
/ CD ROM Paradise Collection 4 / CD ROM Paradise Collection 4 1995 Nov.iso / program / swags_z.zip / SCROLL.SWG / 0012_Smooth Text Scroll.pas < prev    next >
Pascal/Delphi Source File  |  1994-01-27  |  8KB  |  402 lines

  1. {
  2. > Does anybody know if it is possible to accomplish a smooth-text scroller
  3. > (like in the old c64 dayz) in text mode? If so, please let me know and
  4.  
  5. > Well, it's impossible, you'll have to switch to a graphic mode.
  6.  
  7.         No, it's possible in text mode... it's just a pain in the
  8. arse.  I know of two ways.  The first is to use an alternate
  9. character set (the EGA can have 2 on screen at once, the VGA can
  10. have 4).  You use one character set as normal text, and use the
  11. other as a pseudo-graphics window.  Put the text you need to
  12. scroll in the window and move (copy) it a pixel at a time.  The
  13. second way is to use the 8253 timer to time the scanline.  When
  14. the scanline gets to the portion of the screen you want, turn off
  15. v-retrace, set v-retrace on the next scan line, and set the
  16. horizontal pel pan to the value you need for your smooth pan.
  17. When the card gets to the line that the v-retrace would occur, it
  18. resets the pan but doesn't retrace because you turned it off.
  19. After this, reset the registers you changed back to their default
  20. values so the card builds the screen correctly.  This is done on
  21. EVERY screen build.  Needless to say, the pseudo-graphics window
  22. version is easier so that's the one I used to program the example
  23. that follows.
  24. }
  25.  
  26. Program SmoothTextScrollExample1;
  27.  
  28. {==============================================
  29.  
  30.        Smooth Scroll In Text Mode Example
  31.            Programmed by David Dahl
  32.                    12/21/93
  33.    This program and source are PUBLIC DOMAIN
  34.  
  35.  ----------------------------------------------
  36.  
  37.    This example uses a second font to scroll
  38.    the text.  The font definition is changed
  39.    to make the text scroll.  This program
  40.    requires VGA.
  41.  
  42.  ==============================================}
  43.  
  44. Uses  CRT;
  45.  
  46. Type  FontDefType = Array[0..255, 0..31] of Byte;
  47.  
  48. Var   ScrollText : String;
  49.  
  50.       FontDef    : FontDefType;
  51.  
  52. Procedure SetCharWidthTo8; Assembler;
  53. Asm
  54.    { Change To 640 Horz Res }
  55.    MOV DX, $3CC
  56.    IN  AL, DX
  57.    AND AL, Not(4 OR 8)
  58.    MOV DX, $3C2
  59.    OUT DX, AL
  60.  
  61.    { Turn Off Sequence Controller }
  62.    MOV DX, $3C4
  63.    MOV AL, 0
  64.    OUT DX, AL
  65.    MOV DX, $3C5
  66.    MOV AL, 0
  67.    OUT DX, AL
  68.  
  69.    { Reset Sequence Controller }
  70.    MOV DX, $3C4
  71.    MOV AL, 0
  72.    OUT DX, AL
  73.    MOV DX, $3C5
  74.    MOV AL, 3
  75.    OUT DX, AL
  76.  
  77.    { Switch To 8 Pixel Wide Fonts }
  78.    MOV DX, $3C4
  79.    MOV AL, 1
  80.    OUT DX, AL
  81.    MOV DX, $3C5
  82.    IN  AL, DX
  83.    OR  AL, 1
  84.    OUT DX, AL
  85.  
  86.    { Turn Off Sequence Controller }
  87.    MOV DX, $3C4
  88.    MOV AL, 0
  89.    OUT DX, AL
  90.    MOV DX, $3C5
  91.    MOV AL, 0
  92.    OUT DX, AL
  93.  
  94.    { Reset Sequence Controller }
  95.    MOV DX, $3C4
  96.    MOV AL, 0
  97.    OUT DX, AL
  98.    MOV DX, $3C5
  99.    MOV AL, 3
  100.    OUT DX, AL
  101.  
  102.    { Center Screen }
  103.    MOV DX, $3DA
  104.    IN  AL, DX
  105.    MOV DX, $3C0
  106.    MOV AL, $13 OR 32
  107.    OUT DX, AL
  108.    MOV AL, 0
  109.    OUT DX, AL
  110. End;
  111.  
  112. Procedure WriteScrollTextCharacters(Row : Byte);
  113. Var Counter : Word;
  114. Begin
  115.      { Set Fonts 0 & 1 }
  116.      ASM
  117.         MOV BL, 4
  118.         MOV AX, $1103
  119.         INT $10
  120.      END;
  121.  
  122.      { Write Characters }
  123.      For Counter := 0 to 79 do
  124.      Begin
  125.           { Set Characters }
  126.  
  127.           MEM[$B800:(80*2)*Row+(Counter*2)]   := Counter;
  128.           { Set Attribute To Secondary Font }
  129.           MEM[$B800:(80*2)*Row+(Counter*2)+1] :=
  130.              MEM[$B800:(80*2)*Row+(Counter*2)+1] OR 8;
  131.  
  132.      End;
  133.  
  134. End;
  135.  
  136. Procedure FlushKeyBoardBuffer;
  137. Var Key : Char;
  138. Begin
  139.      While KeyPressed do
  140.            Key := ReadKey;
  141. End;
  142.  
  143. Procedure SetAccessToFontMemory; Assembler;
  144. ASM
  145.    { Turn Off Sequence Controller }
  146.    MOV DX, $3C4
  147.    MOV AL, 0
  148.    OUT DX, AL
  149.    MOV DX, $3C5
  150.    MOV AL, 1
  151.    OUT DX, AL
  152.  
  153.    { Reset Sequence Controller }
  154.    MOV DX, $3C4
  155.    MOV AL, 0
  156.    OUT DX, AL
  157.    MOV DX, $3C5
  158.    MOV AL, 3
  159.    OUT DX, AL
  160.  
  161.    { Change From Odd/Even Addressing to Linear }
  162.    MOV DX, $3C4
  163.    MOV AL, 4
  164.    OUT DX, AL
  165.    MOV DX, $3C5
  166.    MOV AL, 7
  167.    OUT DX, AL
  168.  
  169.    { Switch Write Access To Plane 2 }
  170.    MOV DX, $3C4
  171.    MOV AL, 2
  172.    OUT DX, AL
  173.    MOV DX, $3C5
  174.    MOV AL, 4
  175.    OUT DX, AL
  176.  
  177.    { Set Read Map Reg To Plane 2 }
  178.    MOV DX, $3CE
  179.    MOV AL, 4
  180.    OUT DX, AL
  181.    MOV DX, $3CF
  182.    MOV AL, 2
  183.    OUT DX, AL
  184.  
  185.    { Set Graphics Mode Reg }
  186.    MOV DX, $3CE
  187.    MOV AL, 5
  188.    OUT DX, AL
  189.    MOV DX, $3CF
  190.    MOV AL, 0
  191.    OUT DX, AL
  192.  
  193.    { Set Misc. Reg }
  194.    MOV DX, $3CE
  195.    MOV AL, 6
  196.    OUT DX, AL
  197.    MOV DX, $3CF
  198.    MOV AL, 12
  199.    OUT DX, AL
  200. End;
  201.  
  202. Procedure SetAccessToTextMemory; Assembler;
  203. ASM
  204.    { Turn Off Sequence Controller }
  205.    MOV DX, $3C4
  206.    MOV AL, 0
  207.    OUT DX, AL
  208.    MOV DX, $3C5
  209.    MOV AL, 1
  210.    OUT DX, AL
  211.  
  212.    { Reset Sequence Controller }
  213.    MOV DX, $3C4
  214.    MOV AL, 0
  215.    OUT DX, AL
  216.    MOV DX, $3C5
  217.    MOV AL, 3
  218.    OUT DX, AL
  219.  
  220.    { Change To Odd/Even Addressing }
  221.    MOV DX, $3C4
  222.    MOV AL, 4
  223.    OUT DX, AL
  224.    MOV DX, $3C5
  225.    MOV AL, 3
  226.    OUT DX, AL
  227.  
  228.    { Switch Write Access }
  229.    MOV DX, $3C4
  230.    MOV AL, 2
  231.    OUT DX, AL
  232.    MOV DX, $3C5
  233.    MOV AL, 3  {?}
  234.    OUT DX, AL
  235.  
  236.    { Set Read Map Reg }
  237.    MOV DX, $3CE
  238.    MOV AL, 4
  239.    OUT DX, AL
  240.    MOV DX, $3CF
  241.    MOV AL, 0
  242.    OUT DX, AL
  243.  
  244.    { Set Graphics Mode Reg }
  245.    MOV DX, $3CE
  246.    MOV AL, 5
  247.    OUT DX, AL
  248.    MOV DX, $3CF
  249.    MOV AL, $10
  250.    OUT DX, AL
  251.  
  252.    { Set Misc. Reg }
  253.    MOV DX, $3CE
  254.    MOV AL, 6
  255.    OUT DX, AL
  256.    MOV DX, $3CF
  257.    MOV AL, 14
  258.    OUT DX, AL
  259. End;
  260.  
  261. Procedure MakeFontDefTable;
  262. Var  CounterX,
  263.      CounterY  : Word;
  264. Begin
  265.      SetAccessToFontMemory;
  266.  
  267.      For CounterY := 0 to 255 do
  268.          For CounterX := 0 to 31 do
  269.              FontDef[CounterY, CounterX] :=
  270.                  MEM[$B800:(CounterY * 32)+CounterX];
  271.  
  272.      SetAccessToTextMemory;
  273. End;
  274.  
  275. Procedure ClearSecondFontMemory;
  276. Var Counter : Word;
  277. Begin
  278.      SetAccessToFontMemory;
  279.  
  280.      For Counter := 0 to 32 * 256 do
  281.          MEM[$B800:$4000 + Counter] := 0;
  282.  
  283.      SetAccessToTextMemory;
  284. End;
  285.  
  286. Procedure ScrollMessage;
  287. Const CharCol  : Integer = 8;
  288.       Counter  : Byte = 1;
  289.       COUNTERY : Byte = 0;
  290.       PWRTbl   : Array [0..7] of Byte = (1,2,4,8,16,32,64,128);
  291. Begin
  292.      SetAccessToFontMemory;
  293.  
  294.      ASM
  295.         { Wait For Retrace }
  296.         MOV DX, $3DA
  297.         @RT:
  298.          IN   AL, DX
  299.          TEST AL, 8
  300.         JZ @RT
  301.  
  302.         { Scroll Text One Pixel To The Left }
  303.         MOV AX, $B800 + ($4000 / 16)
  304.         MOV ES, AX
  305.         MOV CX, 32
  306.         @Row:
  307.          MOV DI, (79 * 32) - 1
  308.          ADD DI, CX
  309.          SHL byte ptr ES:[DI], 1
  310.          PUSHF
  311.          SUB DI, 32
  312.          POPF
  313.          PUSH CX
  314.          MOV CX, 79
  315.          @Chrs:
  316.           RCL byte ptr ES:[DI], 1
  317.           PUSHF
  318.           SUB DI, 32
  319.           POPF
  320.          Loop @Chrs
  321.          POP CX
  322.         Loop @Row
  323.      END;
  324.  
  325.      If CharCol < 0
  326.      Then
  327.  
  328.      Begin
  329.           CharCol := 7;
  330.           Inc(Counter);
  331.      End
  332.      Else
  333.          Dec(CharCol);
  334.  
  335.      If Counter > Length(ScrollText)
  336.      Then
  337.          Counter := 1;
  338.  
  339.      { Write New Column Of Pixels }
  340.      For CounterY := 0 to 31 do
  341.      MEM[$B800:$4000 + (79 * 32) + CounterY] :=
  342.          MEM[$B800:$4000 + (79 * 32) + CounterY] OR
  343.           ((FontDef[Ord(ScrollText[Counter]), CounterY] AND PwrTbl[CharCol])
  344.             SHR CharCol);
  345.  
  346.      SetAccessToTextMemory;
  347. End;
  348.  
  349. Procedure TurnCursorOff; Assembler;
  350. ASM
  351.    MOV DX, $3D4
  352.    MOV AL, $0A
  353.    OUT DX, AL
  354.    MOV DX, $3D5
  355.    IN  AL, DX
  356.    OR  AL, 32
  357.    OUT DX, AL
  358. End;
  359.  
  360. Procedure TurnCursorOn; Assembler;
  361. ASM
  362.    MOV DX, $3D4
  363.    MOV AL, $0A
  364.    OUT DX, AL
  365.    MOV DX, $3D5
  366.    IN  AL, DX
  367.    AND AL, Not(32)
  368.    OUT DX, AL
  369. End;
  370.  
  371. Begin
  372.      TextMode (C80);
  373.      TurnCursorOff;
  374.      SetCharWidthTo8;
  375.      MakeFontDefTable;
  376.      ClearSecondFontMemory;
  377.      TextColor(Red);
  378.      ClrScr;
  379.  
  380.      ScrollText := 'This program is one example of how a smooth '+
  381.                    'scroll can be done in text mode.            ';
  382.  
  383.      WriteScrollTextCharacters(10);
  384.  
  385.      TextColor(Blue);
  386.      GoToXY (26,10);
  387.      Write  ('Text Mode Smooth Scroll Example');
  388.      GoToXY (34,11);
  389.      Write  ('By David Dahl');
  390.  
  391.      FlushKeyBoardBuffer;
  392.  
  393.      Repeat
  394.            ScrollMessage;
  395.      Until Keypressed;
  396.  
  397.      FlushKeyboardBuffer;
  398.  
  399.      TextMode (C80);
  400.      TurnCursorOn;
  401. End.
  402.